#ifndef VERTEX3D_H
#define VERTEX3D_H

#include <cmath>

class Vertex3D
{
    public:
        Vertex3D(double x = 0, double y=0, double z = 0);
        Vertex3D(const Vertex3D &copy);
        virtual ~Vertex3D();
        double Getx() { return x; }
        void Setx(double val) { x = val; }
        double Gety() { return y; }
        void Sety(double val) { y = val; }
        double Getz() { return z; }
        void Setz(double val) { z = val; }

        double getR(){return sqrt(x*x + y*y + z*z);}


        //operators
        Vertex3D& operator=(const Vertex3D &rhs) {
            this->Setx(rhs.x);
            this->Sety(rhs.y);
            this->Setz(rhs.z);
            return *this;  // Return a reference to myself.
        }
        Vertex3D& operator+=(const Vertex3D &rhs) {
            this->Setx(this->Getx()+rhs.x);
            this->Sety(this->Gety()+rhs.y);
            this->Setz(this->Getz()+rhs.z);
            return *this;
        }
        Vertex3D& operator-=(const Vertex3D &rhs) {
            this->Setx(this->Getx()-rhs.x);
            this->Sety(this->Gety()-rhs.y);
            this->Setz(this->Getz()-rhs.z);
            return *this;
        }
        Vertex3D& operator*=(const double &rhs) {
            this->Setx(this->Getx()*rhs);
            this->Sety(this->Gety()*rhs);
            this->Setz(this->Getz()*rhs);
            return *this;
        }
        Vertex3D& operator/=(const double &rhs) {
            this->Setx(this->Getx()/rhs);
            this->Sety(this->Gety()/rhs);
            this->Setz(this->Getz()/rhs);
            return *this;
        }

        Vertex3D operator+(const Vertex3D &other) const {
            return Vertex3D(*this) += other;
        }
        Vertex3D operator-(const Vertex3D &other) const {
            return Vertex3D(*this) -= other;
        }
        Vertex3D operator*(const double &other) const {
            return Vertex3D(*this) *= other;
        }
        Vertex3D operator/(const double &other) const {
            return Vertex3D(*this) /= other;
        }
        Vertex3D operator-() const {
            return Vertex3D(0, 0, 0) - Vertex3D(*this);
        }

        friend const double operator*(const Vertex3D&, const Vertex3D&);

        friend const double ScalarProduct(const Vertex3D&, const Vertex3D&);

        friend const Vertex3D CrossProduct(const Vertex3D&, const Vertex3D&);


    protected:

    private:
        double x;
        double y;
        double z;
};
#endif // VERTEX3D_H
